/**
 * Created by wdj on 16/4/21.
 * framework7.ext.js
 */

/**
 * 对 framework7 的扩展
 * 目前扩展了 dom7(类似jquery) 的功能
 */
(function($){
    function isDocument(obj)   { return obj != null && obj.nodeType == obj.DOCUMENT_NODE }
    function __extend(destination, source) {
        for (var property in source){
            destination[property] = source[property];
        }
        return destination;
    }
    function __random(start, end){
        end = end || start + start;
        return Math.round(Math.random() * (end - start)) + start
    }

    $.matches = function(element, selector) {
        if (!selector || !element || element.nodeType !== 1) return false;
        var matchesSelector = element.webkitMatchesSelector || element.mozMatchesSelector ||
            element.oMatchesSelector || element.matchesSelector;
        if (matchesSelector) return matchesSelector.call(element, selector);
        // fall back to performing a selector:
        var match, parent = element.parentNode, temp = !parent;
        if (temp) (parent = tempParent).appendChild(element);
        match = ~$(parent, selector).indexOf(element);
        temp && tempParent.removeChild(element);
        return match;
    };

    $.fn.closest = function(selector, context){
        if(!this.length)return;
        var node = this[0], collection = false;
        if (typeof selector == 'object') collection = $(selector);
        while (node && !(collection ? collection.indexOf(node) >= 0 : $.matches(node, selector)))
            node = node !== context && !isDocument(node) && node.parentNode
        return $(node)
    };

    $.fn.siblings = function(){
        if(!this.length)return;
        return $(this).parent().children();
    };

    $.fn.wrap = function(html){
        if(!this.length)return ;
        if(typeof html === "function")html = html();
        var wrap = function(){
            if(document.createRange){
                var range = document.createRange();
                range.setStartAfter(document.body);
                return range.createContextualFragment(html)
            }else{
                return document.createElement(html)
            }
        }();
        this[0].parentNode.insertBefore(wrap, this[0]);
        this[0].previousSibling.appendChild(this[0]);
    };

    $.fn.hasData = function(name){
        return $(this).data(name) != null;
    };

    $.fn.hasAttribute = function(name){
        return $(this).attr(name) != null;
    };

    /**
     * 基于 animate.css 动画的封装
     * 动画效果参考 http://daneden.github.io/animate.css/
     * @param {String} animatedName 动画名
     * @param {Function} callback
     */
    $.fn.animated = function(animatedName, callback){
        var el = this;
        var a = ('animated ' + animatedName).replace(/\s+/g,' ');
        $(el).animationEnd(function(){
            $(el).removeClass(a);
            typeof(callback) === "function" && callback.call(el);
        });
        $(el).addClass(a);

    };


    //////////////////////////////////////////
    /**
     * 对 app 扩展
     * @param app
     * @param params
     * @returns {{hooks: {}}}
     */
    Framework7.prototype.plugins.appExt = function(app, params){
        var appExt = {
            /**
             * 全局事件绑定
             * 必须保证选择器在整个应用中都不重复，否则出现绑定多个dom
             * @param bindings
             */
            bindEvents: function (bindings) {
                for (var k in bindings) {
                    var s = k.split(' ');
                    var e = s.shift();
                    $(s.join(' ')).on(e, bindings[k]);
                }
            },

            hasDevice: function(options){
                options = __extend({
                    weixin: null,
                    android: null,
                    ios: null,
                    h5: null
                }, options);
                if(options.h5 && !native.device.isNative && !native.device.weixin){
                    options.h5.call(this);
                }else {
                    if(native.device.weixin){
                        options.weixin && options.weixin.call(this);
                    }else if(options.android && native.device.android && native.device.isNative){
                        options.android.call(this);
                    }else if(options.ios && native.device.ios && native.device.isNative){
                        options.ios.call(this);
                    }
                }
            },
            /**
             * 显示 modal
             * 基于 framework7 modal
             * @param options
             */
            showModal: function(options){
                options = __extend({
                    autoClose: 0,
                    clickClose: false,
                    onClose: null,
                    onClosed: null,
                    animate: true
                }, options);
                var m = app.modal(options);
                var $m =  $(m);
                $m.css({
                    zIndex: 100000
                }).on('closed', function(){
                    typeof options.onClosed === "function" && options.onClosed.call(this);
                }).on('close', function(){
                    typeof options.onClose === "function" && options.onClose.call(this);
                });
                if(options.autoClose){
                    setTimeout(function(){
                        close();
                    }, options.autoClose);
                }
                if(options.clickClose){
                    var overlay = $('.modal-overlay');
                    var f = function(){
                        close();
                        overlay.off('click', f);
                    };
                    overlay.on('click', f);
                }
                function close(){
                    /*var animate = ['fadeOutRight','hinge','zoomOut','fadeOutUpBig','hinge'];
                     if((app.device.android && app.device.osVersion < '4.4') || !options.animate){
                     app.closeModal($m);
                     }else{
                     $m.animated(animate[__random(0, animate.length - 1)], function(){
                     app.closeModal($m);
                     $m.remove();
                     });
                     }*/
                    app.closeModal($m);
                    $m.remove();
                }
                return m;
            },

            /**
             * 显示提示
             * 基于 showModal 支持所有 modal 选项
             * @param options
             * @param {Integer} [autoCloseTime]
             */
            showTips: function(options, autoCloseTime){
                if(typeof options === "string"){
                    options = {
                        text: options
                    };
                }
                if(autoCloseTime && typeof autoCloseTime === 'number'){
                    options.autoClose = autoCloseTime;
                }
                options = __extend({
                    clickClose: true,
                    fontSize: 16,
                    color: 'orangered'
                }, options);
                options.text = '<span style="color:' + (options.color) + ';font-size: ' + (options.fontSize || 16) + 'px;">' + (options.text || '') + '</span>';
                return this.showModal(options);
            },
            showToast: function(message){
                message = String(message).replace(/<br.*?>/g,'\n');
                if(window.Hybrid && Hybrid.isNative){
                    window.Hybrid.showToast(message);
                }else{
                    var tpl = $('<div class="toast toast-black">' + message + '</div>');
                    $('body').append(tpl);
                    tpl.animated('fadeIn');
                    tpl.css({
                        opacity: 1,
                        left: (($(window).width() - tpl.width()) / 2) + 'px'
                    });
                    setTimeout(function(){
                        tpl.animated('fadeOut', function(){
                            tpl.remove();
                        });
                    }, 3000);
                }
            },
            cnCalendar: function(params){
                params = __extend({
                    dateFormat: 'yyyy-mm-dd',
                    monthNames: ['一月', '二月', '三月', '四月', '五月', '六月', '七月', '八月' , '九月' , '十月', '十一月', '十二月'],
                    monthNamesShort: ['一', '二', '三', '四', '五', '六', '七', '八' , '九' , '十', '十一', '十二'],
                    dayNames: ['星期日', '星期一', '星期二', '星期三', '星期四', '星期五', '星期六'],
                    dayNamesShort: ['日', '一', '二', '三', '四', '五', '六']
                }, params);
                return app.calendar(params);
            },

            /**
             * 一键分享
             * @param options
             * @param callback
             */
            oneKeyShare: function(options, callback){
                var self = this;
                if(window.Hybrid && Hybrid.device.isNative){
                    self.showIndicator();
                    setTimeout(function(){
                        self.hideIndicator();
                    },1000);
                    if(options.url){
                        getShareURL(options.url, function(url){
                            options.url = url;
                            if(options.titleUrl){
                                getShareURL(options.titleUrl, function(url){
                                    options.titleUrl = url;
                                    native.widget.oneKeyShare(options, callback);
                                });
                            }else{
                                native.widget.oneKeyShare(options, callback);
                            }
                        });
                    }else{
                        native.widget.oneKeyShare(options, callback);
                    }
                }else{
                    var m = app.showModal({
                        cssClass: 'sharePopupTips',
                        clickClose: true,
                        text: '<div class="list-block" style="margin:0;overflow-y:auto;max-height: 400.2px;">\
            <img src="image/hot_03.png" width="100%"/>\
                <p class="tc" style=" color: #ffffff; font-size: 1.3rem; margin-top: 30px; margin-bottom: 10px;">人人可参与，天天领补贴</p>\
            <img src="image/hot_04.png" width="50%" class="download_app_link"/>\
                </div>'
                    });
                    app.query(m).find('.download_app_link').click(function(){
                        var id = 'msjzv2_android';
                        if(native.device.ios){
                            id = 'msjzv2_ios';
                        }
                        location.href = app.Config.appDownloadUrl + id;
                    });
                }

                function getShareURL(url, callback){
                    if(url && typeof url === 'string'){
                        var userId = self.utils.Storage.get("MEMBER_INFO");
                        if(userId){
                            userId = userId.userId || 0;
                        }
                        if(userId && url.indexOf('_shareUid') === -1){
                            url = app.utils.setUrlParameter('_shareUid', userId, url);
                        }
                        if(url.indexOf('url.cn') === -1){
                            self.utils.getShortUrl(url, function(url){
                                callback(url);
                            });
                            return;
                        }
                    }
                    callback(url);
                }
            },
            clearStorage: function(){
                for(var key in window.localStorage){
                    if(key == 'STORAGE_MEMBER_INFO' || key == 'STORAGE_USER_DETAILS'){
                        continue;
                    }
                    window.localStorage.removeItem(key);
                }
            }

        };

        __extend(app, appExt);



        $.fn.calendar = function(options){
            var monthNames = ['一月', '二月', '三月', '四月', '五月', '六月', '七月', '八月' , '九月' , '十月', '十一月', '十二月'];
            options = __extend({
                input: this,
                value:  []
            }, options);

            if(options.toolbarTemplate === true){
                options.toolbarTemplate = '<div class="toolbar calendar-custom-toolbar">' +
                    '<div class="toolbar-inner">' +
                    '<div class="left">' +
                    '<a href="#" class="link icon-only"><i class="icon icon-back"></i></a>' +
                    '</div>' +
                    '<div class="center"></div>' +
                    '<div class="right">' +
                    '<a href="#" class="link icon-only"><i class="icon icon-forward"></i></a>' +
                    '</div>' +
                    '</div>' +
                    '</div>';

                options.onOpen = function(p){
                    var calendarInline = p;
                    $('.calendar-custom-toolbar .center').text(p.currentYear + '年 ,' + monthNames[p.currentMonth]);
                    $('.calendar-custom-toolbar .left .link').on('click', function () {
                        calendarInline.prevMonth();
                    });
                    $('.calendar-custom-toolbar .right .link').on('click', function () {
                        calendarInline.nextMonth();
                    });
                };

                options.onMonthYearChangeStart = function (p) {
                    $('.calendar-custom-toolbar .center').text(p.currentYear + '年 ,' + monthNames[p.currentMonth]);
                };
            }
            if(this.val() && this.val().length > 0){
                var val = this.val().split(',');
                options.value = val;
            }
            appExt.cnCalendar(options);
        };

        $.fn.popupSelect = function(options){
            var maxHeight = $(window).height() * 0.6;
            $(this).each(function(){
                var select  = this,
                    selectName = select.name,
                    selectValue = select.value,
                    selectTitle = $(select).data('select-title') || '请选择';

                var html = '<div class="list-block" style="margin:0;overflow-y:auto;max-height: '+maxHeight+'px;"><ul style="background-color: transparent;">' +
                    '{{#each options}}' +
                    '<li><label class="label-radio item-content"><input type="radio" name="{{name}}" value="{{value}}" {{checked}}><div class="item-inner"><div class="item-title">{{label}}</div></div></label></li>'+
                    '{{/each}}' +
                    '</ul></div>';
                var selectOptions = [], kv = {};
                for (var i = 0; i < select.options.length; i++) {
                    var row = select.options[i];
                    if (row.value && row.value !== ' ') {
                        kv[row.value] = row.innerText;
                        selectOptions.push({
                            name: selectName,
                            label: row.innerText,
                            value: row.value,
                            checked: selectValue == row.value ? 'checked' : ''
                        });
                    }
                }

                var newChild = $(`<input name="${selectName}" type="text" value="${kv[selectValue]||''}" readonly="readonly" placeholder="请选择"/>`);
                newChild.insertAfter(select);
                $(select).remove();

                newChild.click(function(){
                    selectValue = newChild.val();
                    selectOptions.forEach(function( row,i){
                        row.checked = (selectValue == row.value ? 'checked' : '');
                    });
                    var tpl = Template7.compile(html)({options: selectOptions});
                    var isShowButton = options && typeof options.isShowButton !== "undefined" ? options.isShowButton : true;
                    var modalOptions = {
                        title: selectTitle,
                        text: tpl
                    };

                    if(isShowButton){
                        modalOptions.buttons = [
                            {
                                text: '确认',
                                onClick: function(m){
                                    var selected = m.find(`input[name="${selectName}"]:checked`).val();
                                    if(options && options.onChange){
                                        options.onChange.call(select, selected, kv[selected]);
                                    }
                                    //$(select).val(selected);
                                    selectValue = selected;
                                    newChild.val(kv[selected]);
                                }
                            }
                        ]
                    }

                    var m = app.modal(modalOptions);
                    if(!isShowButton){
                        $(m).find('li').on('click', function(){
                            var selected = $(this).find('input[type="radio"]').val();
                            if(options && options.onChange){
                                options.onChange.call(select, selected, kv[selected]);
                            }
                            //$(select).val(selected);
                            selectValue = selected;
                            newChild.val(kv[selected]);
                            app.closeModal(m);
                        });
                    }

                    return false;
                });
            });
        };

        $.fn.popoverSelect = function (options) {

            options = __extend({
                width: 'auto',
                labelCssClass: ''
            }, options);

            var tpl = '<div class="popover" style="width: {{width}};">\
                <div class="popover-angle"></div>\
                <div class="popover-inner">\
                <div class="list-block">\
                <ul>'+
                '{{#each options}}' +
                '<li><label class="label-radio item-content"><input type="radio" name="{{name}}" value="{{value}}" {{checked}}><div class="item-inner"><div class="item-title">{{label}}</div></div></label></li>'+
                '{{/each}}' +
                '</ul>\
                </div>\
                </div>\
                </div>';

            $(this).each(function(){
                var select  = this;
                var selectOptions = [], kv = {};
                for (var i = 0; i < select.options.length; i++) {
                    var row = select.options[i];
                    if (row.value) {
                        kv[row.value] = row.innerText;
                        selectOptions.push({
                            name: select.name,
                            label: row.innerText,
                            value: row.value,
                            checked: select.value == row.value ? 'checked' : ''
                        });
                    }
                }
                var newChild = $('<a class="' + options.labelCssClass + '" href="#">' + (kv[select.value]||'') + '</a>');
                newChild.insertAfter(select);
                $(select).hide();
                newChild.click(function(){
                    selectOptions.forEach(function(row,i){
                        row.checked = (select.value == row.value ? 'checked' : '');
                    });
                    var html = Template7.compile(tpl)({
                        options:selectOptions,
                        width: options.width
                    });
                    var pop = app.popover(html, this);
                    $(pop).find('li').on('click',function(){
                        var selected = $(this).find('input[name="'+select.name+'"]').val();
                        if(selected){
                            $(select).val(selected);
                            newChild.text(kv[selected]);
                            app.closeModal(pop);
                        }
                    });
                });
            });
        };

        $.fn.pickerInline = function (options) {
            this.each(function(){
                var $this = $(this);
                var today = new Date();
                var valueDate = new Date($this.val() != '' ? $this.val() : today);
                var minYear = Math.max(options.minDate ? options.minDate.getFullYear() : 0, 1950);
                var maxYear = options.maxDate ? options.maxDate.getFullYear() : 2099;

                options = __extend({
                    input: this,
                    value: [valueDate.getFullYear(), valueDate.getMonth(), valueDate.getDate(), valueDate.getHours(), (valueDate.getMinutes() < 10 ? '0' + valueDate.getMinutes() : valueDate.getMinutes())],
                    toolbar: true,
                    rotateEffect: app.device.ios ,
                    onChange: function (picker, values, displayValues) {
                        var daysInMonth = new Date(picker.value[0], picker.value[1] * 1 + 1, 0).getDate();
                        if (values[2] > daysInMonth) {
                            picker.cols[2].setValue(daysInMonth);
                        }
                        if (values[0] < minYear) {
                            picker.cols[0].setValue(minYear);
                        }
                        if (values[0] > maxYear) {
                            picker.cols[0].setValue(maxYear);
                        }
                    },
                    formatValue: function (p, values, displayValues) {
                        return app.utils.dateFormat(new Date(values[0], values[1], values[2], values[3], values[4]), options.dateFormat || 'yyyy-MM-dd hh:mm')
                    },
                    cols: [
                        // Years
                        {
                            values: (function () {
                                var arr = [];
                                for (var i = 1950; i <= 2099; i++) {
                                    arr.push(i);
                                }
                                return arr;
                            })(),
                            displayValues: (function () {
                                var arr = [];
                                for (var i = 1950; i <= 2099; i++) {
                                    arr.push(i);
                                }
                                return arr;
                            })()
                        },
                        // Months
                        {
                            values: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11],
                            //displayValues: ['一月', '二月', '三月', '四月', '五月', '六月', '七月', '八月', '九月', '十月', '十一月', '十二月'],
                            displayValues: [1,2,3,4,5,6,7,8,9,10,11,12],
                            textAlign: 'left'
                        },
                        // Days
                        {
                            values: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31],
                            displayValues: (function () {
                                var arr = [];
                                for (var i = 1; i <= 31; i++) {
                                    arr.push(i)
                                }
                                return arr;
                            })()
                        },
                        // Space divider
                        {
                            divider: true,
                            content: '&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;'
                        },
                        // Hours
                        {
                            values: (function () {
                                var arr = [];
                                for (var i = 0; i <= 23; i++) {
                                    arr.push(i);
                                }
                                return arr;
                            })()
                        },
                        // Divider
                        {
                            divider: true,
                            content: ':&nbsp;'
                        },
                        // Minutes
                        {
                            values: (function () {
                                var arr = [];
                                for (var i = 0; i <= 59; i++) {
                                    arr.push(i < 10 ? '0' + i : i);
                                }
                                return arr;
                            })()
                        }
                    ]
                }, options);
                app.picker(options);
            });
            //return app.picker(options);
        };

        ///

        (function(){
            var cssClasss = [];
            if(app.device.android && app.device.osVersion < '4.4'){
                cssClasss.push('android-lt-4-4');
            }else{
                app.device.android && cssClasss.push('android-egt-4-4');
            }

            if(window.native){
                if(native.device.isNative){
                    cssClasss.push('native');
                }
                if(native.device.weixin){
                    cssClasss.push('weixin');
                    cssClasss.push('weixin-' + String(native.device.weixinVersion).replace(/\./g,'-'));
                }
            }
            cssClasss.length && $('html').addClass(cssClasss.join(' '));
        })();


        //////////////////////////////////////////
        //对 Template7 扩展

        /**
         * 在模板中使用  obj[attr] 方式读取变量.
         * 使用方式 {{array obj attr}}, * attr 必须是一个变量
         */
        Template7.registerHelper('array', function (arr, options) {
            if (typeof arr === 'function') arr = arr.call(this);
            return arr[options];
        });

        /**
         * 在模板中解析图片
         * 使用方式 {{img logoUrl}}
         */
        Template7.registerHelper('img', function (src, options) {
            if (typeof src === 'function') src = src.call(this);
            if(!src)return app.Config.errorImage;
            if(app.Config){
                src = app.Config.getImageUrlPath() + '?key=' + src;
            }
            return src;
        });

        Template7.registerHelper('image', function (src, options) {
            if (typeof src === 'function') src = src.call(this);
            var imgError = false;
            if(app.Config){
                if(src){
                    src = app.Config.getImageUrlPath() + '?key=' + src;
                }else{
                    if(options.hash && options.hash.taskImage){
                        src = app.Config.taskErrorImage;
                    }else{
                        src = app.Config.errorImage;
                    }
                    imgError = true;
                }
            }
            var attr = [];
            if(options.hash){
                if(options.hash.width){
                    attr.push('width="' + options.hash.width + '"');
                    if(!imgError){
                        src += "&Width="+options.hash.width;
                    }
                }
                if(options.hash.height){
                    attr.push('height="' + options.hash.height +'"');
                    if(!imgError) {
                        src += "&Height=" + options.hash.height;
                    }
                }
                if(options.hash.cssClass){
                    attr.push('class="' + options.hash.cssClass +'"');
                }
                if(options.hash.style){
                    attr.push('style="' + options.hash.style +'"');
                }
            }
            return '<img src="' + src + '" ' + attr.join(' ') + ' onerror="this.src=\'' + app.Config.errorImage + '\'"/>';
        });

        /**
         * 时间格式化
         * 使用方式 {{dateFormat formatSendTime "hh:mm"}}
         */
        Template7.registerHelper('dateFormat', function (date, format, options) {
            if (typeof date === 'function') date = date.call(this);
            if(options.hash.format){
                format = options.hash.format;
            }
            if(typeof date === 'string' && date.indexOf('-') > -1){
                date = date.replace(/-/g,'/');
            }
            if(options.hash.today){
                var sdate = new Date(date), now = new Date();
                var d = app.utils.dateDiff(sdate, now, 'd');
                if(d == 0){
                    format = options.hash.today;
                }
            }
            return app.utils.dateFormat(date, format);
        });

        /**
         * 去除html标签
         * 使用方式 {{strTags messageContent}}
         */
        Template7.registerHelper('strTags', function (str, options) {
            if (typeof str === 'function') str = str.call(this);
            return app.utils.str_tags(str);
        });

        Template7.registerHelper('join', function (arr, options) {
            if (typeof arr === 'function') arr = arr.call(this);
            return arr.join(options.hash.delimiter);
        });

        Template7.registerHelper('forEach', function(condition, options){
            var contents = [];
            var limit = options.hash.limit || 0;
            if(app.utils.isArray(condition)){
                var len =  Math.min(parseInt(limit), condition.length);
                for (var i = 0; i < len; i++) {
                    var row = condition[i];
                    contents.push(options.fn(row, {
                        key: i,
                        index: i,
                        first: i == 0,
                        last: i == len
                    }));
                }
            }else if(condition){
                var i = 0;
                for(var k in condition){
                    if(limit && ++i > parseInt(limit)){
                        break;
                    }
                    contents.push(options.fn(condition[k], {
                        key: k,
                        index: i - 1,
                        first: i - 1 == 0
                    }));
                }
            }
            return contents.join('\n');
        });

        Template7.registerHelper('nl2br', function(str, options){
            return app.utils.nl2br(str);
        });

        // 插件钩子
        return {
            hooks: {
                appInit: function(){

                },
                pageAfterAnimation: function(page){

                }
            }
        }
    }

})(Dom7);
